﻿using System;
using System.Linq;

using AutoMapper;

using Microsoft.EntityFrameworkCore;

using Xc.DataAccess.Core;
using Xc.DataAccess.Core.Services;
using Xc.DataAccess.DataBase.DeviceInfos.Models;

namespace Xc.DataAccess.DataBase.DeviceInfos
{
    /// <summary>
    /// 设备命令信息服务
    /// </summary>
    public class DbCommandInfoService<TDbContext> : IDbCommandInfoService where TDbContext : DbContext, IDbDevice
    {
        private readonly IDbContextFactory<TDbContext> _dbContextFactory;
        private readonly IConverterService converterService;
        private readonly IMapper mapper;
        public DbCommandInfoService(IDbContextFactory<TDbContext> dbContextFactory, IConverterService converterService, IMapper mapper)
        {
            _dbContextFactory = dbContextFactory;
            this.converterService = converterService;
            this.mapper = mapper;
        }
        /// <summary>
        /// 推送命令到缓冲
        /// </summary>
        /// <param name="deviceInfoAdd">要添加的命令</param>
        /// <returns></returns>
        public Result Push(CommandInfoAdd deviceInfoAdd)
        {
            using var db = _dbContextFactory.CreateDbContext();
            var inf = db.DeviceInfos.Where(p => p.Id == deviceInfoAdd.DeviceInfoId).FirstOrDefault();
            if (inf==null)
            {
                return Result.Reject($"请先注册表信息,编号:{deviceInfoAdd.DeviceInfoId}");
            }

           var info = mapper.Map<CommandInfo>(deviceInfoAdd);
            info.Status = CommandStatus.待发送;
            info.RespondInfo = null;
            db.CommandInfos.Add(info);
            return Result.From(db.SaveChanges(), n => n > 0);
        }
        /// <summary>
        /// 获取最新的一条数据
        /// </summary>
        /// <param name="deviceInfoId"></param>
        /// <returns></returns>
        public ResultData<CommandInfo, SendState> Peek(string deviceInfoId)
        {
            using var db = _dbContextFactory.CreateDbContext();
            var inf = db.CommandInfos.Where(p => p.DeviceInfoId == deviceInfoId && p.Status == CommandStatus.待发送).FirstOrDefault();
            if (inf != null)
            {
                return ResultData<CommandInfo, SendState>.Accept("查询成功", inf, SendState.HasData);
            }
            else
            {
                return ResultData<CommandInfo, SendState>.Accept("无待发送的命令", inf, SendState.NoData);
            }
        }
        /// <summary>
        /// 删除设备下的所有命令
        /// </summary>
        /// <param name="deviceInfoId"></param>
        /// <returns></returns>
        public Result CancelCommands(string deviceInfoId)
        {
            using var db = _dbContextFactory.CreateDbContext();
            var datas=  db.CommandInfos.Where(p => p.DeviceInfoId == deviceInfoId);
            db.CommandInfos.RemoveRange(datas);
            return Result.From(db.SaveChanges(), n => n > 0);
        }
        /// <summary>
        /// 获取命令列表
        /// </summary>
        /// <param name="deviceInfoId"></param>
        /// <param name="days"></param>
        /// <returns></returns>
        public ResultData<CommandInfo[]> Gets(string deviceInfoId, int? days)
        {
            try
            {
                using var db = _dbContextFactory.CreateDbContext();
                IQueryable<CommandInfo> query = db.CommandInfos;
                if (!string.IsNullOrEmpty(deviceInfoId))
                {
                    query = query.Where(p => p.DeviceInfoId == deviceInfoId);
                }
                var dt = days.HasValue ? DateTime.Now.AddDays(-days.Value) : DateTime.Now.AddDays(-7);
                query = query.Where(p => p.RequestInfo.CreateDateTime > dt);
                return ResultData<CommandInfo[]>.Accept("查询成功", query.ToArray());
            }
            catch (Exception err)
            {
                return ResultData<CommandInfo[]>.Reject(err.Message,null);
            }

        }
        /// <summary>
        /// 更新命令信息
        /// </summary>
        /// <param name="commandInfo"></param>
        /// <returns></returns>
        public Result Update(CommandInfo commandInfo)
        {
            using var db = _dbContextFactory.CreateDbContext();
            var cmd = db.CommandInfos.Where(p => p.CommandId == commandInfo.CommandId).FirstOrDefault();
            if (cmd == null)
            {
                return Result.Reject("要更新的被不存在");
            }
            else
            {
                return Result.From(db.SaveChanges(), n => n > 0);
            }
        }

        public Result CancelCommand( Guid commandId)
        {
            using var db = _dbContextFactory.CreateDbContext();
            var datas = db.CommandInfos.Where(p =>p.CommandId==commandId);
            db.CommandInfos.RemoveRange(datas);
            return Result.From(db.SaveChanges(), n => n > 0);
        }
    }

}
